package com.zkh.myutils.scheduled;

import java.sql.Timestamp;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import com.zkh.myutils.database.conutils.PoolUtils;
import com.zkh.myutils.database.data.QueryRunner;
import com.zkh.myutils.database.dbpool.ConnectConfigure;
import com.zkh.myutils.database.dbpool.DBType;
import com.zkh.myutils.io.log.Logger;
import com.zkh.myutils.utils.ArrayUtils;
import com.zkh.myutils.utils.CollectionUtils;

/**
 * 任务相关数据库操作
 * @author zkh
 */
class ScheduledTaskService {
	
	//数据库类型
	private DBType type;
	
	//数据库操作对象
	private QueryRunner qr = new QueryRunner(PoolUtils.getDataSource());
	
	//获取日期
	private Date getDate() {
		return DBType.TYPE_MYSQL.equals(type) ? new Date() : new Timestamp(System.currentTimeMillis());
	}

	/**
	 * 初始化数据库相关表
	 */
	void createTable() {
		// 数据库类型
		type = ConnectConfigure.getDefaultSourceConfig().getDbtype();
		//定时SQL
		String[] ddlSqls = ScheduledTaskTableDDL.getTableDDL(type);
		// 执行DDL
		ArrayUtils.forEach(ddlSqls, (ddlSql, idx)->qr.update(ddlSql.replace("{prefix}", ScheduledTaskScanner.getTaskRecordTablePre())));
	}
	
	/**
	 * 保存任务定义
	 */
	void saveTaskDef(List<ScheduledTaskConfig> configList) {
		//批量添加参数
		Object[][] params = new Object[configList.size()][];
		//获取任务编码
		List<String> jobEcdList = new ArrayList<String>();
		//遍历值
		for(int i=0,len=configList.size(); i<len; i++) {
			//当前
			ScheduledTaskConfig e = configList.get(i);
			//保存任务代码
			jobEcdList.add(e.getJobEcd());
			//保存批量参数(jobEcd, jobDesc, cronExp, jobBeanName, jobParam, createTime)
			params[i] = new Object[]{e.getJobEcd(), e.getJobDesc(), e.getCronExp(), e.getJobBeanName(), e.getJobParam(), getDate()};
		}
		//删除已有记录
		CollectionUtils.split(jobEcdList, 999).forEach(list->{
			//SQL
			String sql = "DELETE FROM " + ScheduledTaskScanner.getTaskRecordTablePre() + "timer_task_def WHERE jobEcd IN (" + String.join(",", ArrayUtils.getArray(String.class, list.size(), "?")) + ")";
			//保存
			qr.update(sql, list.toArray());
		});
		//插入SQL
		String insert = ScheduledTaskTableDDL.getInsertSQL().replace("{prefix}", ScheduledTaskScanner.getTaskRecordTablePre());
		//遍历组装参数
		qr.batch(insert, params);
	}

	/**
	 * 保存任务开始执行状态
	 * @param config 配置
	 */
	boolean saveBegin(ScheduledTaskConfig config, long time) {
		//新增SQL
		String insert = "INSERT INTO " + ScheduledTaskScanner.getTaskRecordTablePre() + "timer_task_record (jobEcd, executeTime, executeType, startTime, execState) VALUES (?, ?, 0, ?, 1)";
		try {
			//插入一条记录
			qr.update(insert, config.getJobEcd(), time, getDate());
			//成功标识
			return true;
		}catch(Exception e) {
			//输出日志
			Logger.error(e);
			//发生异常，视为主键冲突，直接跳过
			return false;
		}
	}

	/**
	 * 保存任务执行结束状态
	 * @param config 配置
	 * @param success 成功状态。1：成功，0：失败
	 * @param msg 执行结束信息
	 */
	void saveFinished(ScheduledTaskConfig config, long time, int success, String msg) {
		//更新SQL
		String update = "UPDATE " + ScheduledTaskScanner.getTaskRecordTablePre() + "timer_task_record SET endTime=?,execParam=?,execState=?,execResult=? WHERE jobEcd=? AND executeTime=?";
		//执行更新
		qr.update(update, getDate(), config.getJobParamJson().toString(), success==1 ? 2 : 3, msg, config.getJobEcd(), time);
	}
}
